# -*- coding:utf-8 -*-
import os,sys
import re
import traceback
import time
sys.path.append(os.path.join(os.path.abspath(os.path.dirname(__file__)), os.pardir, os.pardir))
import supeanut_config
sys.path.append(os.path.join(os.path.abspath(os.path.dirname(__file__)), os.pardir))
from CommonLib.mylog import mylog


'''
作者：supeanut
创建时间：2016-12-13 12:37
功能描述：
	输入list，写入csv
	【注意事项】record不能有半角逗号！
	此脚本保持正常运行的前提：对于同一个文件，所有记录的colum数不变且外部colum数也保持一致
	新建csv文件：可选强制写入
	更新csv文件：在指定index下更新数据，包括append，其中更新只针对第一条匹配index的record
	append写入：对指定csv文件，在末尾添加新数据record
相关配置：
	supeanut_config.XXX
历史改动：
	2016-xx-xx: xxxxxx
'''
class CsvTool:
	def __init__(self):
		pass

	# 读取csv文件，返回list[list]形式（utf-8）
	def read_csv(self, csv_path, csv_name):
		complete_path = os.path.join(csv_path, csv_name)
		if not os.path.isfile(complete_path):
			return False, 'no such file: %s'%complete_path
		try:
			csv = open(complete_path, 'rb')
			records = csv.readlines()
			csv.close()
		except:
			return False, traceback.format_exc()
		result = []
		for record in records:
			record_split = record.split(',')
			# 去\n
			record_split[-1] = record_split[-1][:-1]
			# 去^M
			if record_split[-1][-1] == '\r':
				record_split[-1] = record_split[-1][:-1]
			result.append(record_split)
		return True, result

	# 验证csv文件是否列对齐
	# 只有在返回False且msg=‘verify failed’，才能判断没对齐
	# 指定colume_num = n时，按照列数标准验证
	def verify_csv(self, csv_path, csv_name, colume_num = -1):
		complete_path = os.path.join(csv_path, csv_name)
		if not os.path.isfile(complete_path):
			return False, 'no such file: %s'%complete_path
		try:
			csv = open(complete_path, 'rb')
			records = csv.readlines()
			csv.close()
		except:
			return False, traceback.format_exc()
		if not isinstance(records,list):
			return False, 'read csv, no list return'
		if len(records) <= 1:
			return True, 'verify suc or nothing in csv or only one line'
		record_0 = records[0]
		if colume_num >= 1:
			base_len = colume_num
		else:
			base_len = len(record_0.split(','))
		for record in records:
			record_split = record.split(',')
			record_len = len(record_split)
			if base_len <> record_len:
				return False, 'verify failed'
		return True, 'verify suc'

	# INPUT: [['A','123'],['B','456']]
	# OUTPUT:['A,123\n','B,456\n']
	def record_list2str_list(self, record_list):
		record_str_list = []
		for record in record_list:
			record_str = ''
			for colum in record:
				record_str += (colum + ',')
			record_str = record_str[:-1]
			record_str += '\n'
			record_str_list.append(record_str)
		return record_str_list
		
	# 新建csv文件
	# INPUT: 绝对路径file_path, 文件名file_name
	#        [['a','b'],...],record必须是utf-8格式
	#        forcetag：强制写入
	# OUTPUT: flag，msg
	def new_csvfile(self, record_list, file_path, file_name, force_tag=False):
		complete_path = os.path.join(file_path, file_name)
		# 判断源文件是否存在
		if os.path.exists(complete_path) and force_tag is False:
			# 引用在DataSupport.BasicDataSupoort
			return False, 'file already exists'
		if not os.path.exists(file_path):
			# 创建路径
			try:
				os.makedirs(file_path)
			except OSError, e:
				return False, 'create path failed: %s'%e
		# 组合成str_list格式
		record_str_list = self.record_list2str_list(record_list)
		# 写入新文件中
		try:
			csv_file = open(complete_path, 'wb')
			csv_file.writelines(record_str_list)
			csv_file.close()
		except IOError, e:
			return False, 'file write failed: %s'%e
		return True, 'suc'
	
	# 更新旧csv文件,默认旧文件存在
	# 增修模式，无删
	# 只更新一个record，即默认index_list为主键且只有一个记录
	# 输入index_list [0,2]，代表主键为第1第3个
	def update_csvfile(self, index_list, record_list, file_path, file_name):
		complete_path = os.path.join(file_path, file_name)
		# 新建文件
		if not os.path.exists(complete_path):
			flag, msg = self.new_csvfile(record_list, file_path, file_name, True)
			return flag, msg
		# 读取旧数据
		old_file = open(complete_path, 'rb')
		old_record_str_list = old_file.readlines()
		old_file.close()
		old_record_list = []
		for old_record_str in old_record_str_list:
			old_record = old_record_str.split(',')
			# 去'\n'
			old_record[-1] = old_record[-1][:-1]
			old_record_list.append(old_record)
		# 查找更新old_record_list
		old_record_list_len = len(old_record_list)
		for record in record_list:
			find_tag = False
			# 只在原记录中找，添加的记录不再寻找目标中
			for old_record_index in range(old_record_list_len):
				# 是否匹配index
				old_record = old_record_list[old_record_index]
				equal_tag = True
				for index in index_list:
					if record[index] <> old_record[index]:
						equal_tag = False
						break
				if equal_tag == True:
					find_tag = True
					# 更新old_record_list
					old_record_list[old_record_index] = record
					# 只更新找到的第一个record
					break
			if find_tag is False:
				# append到old_record_list
				old_record_list.append(record)
		# 覆盖写入
		flag, msg = self.new_csvfile(old_record_list, file_path, file_name, True)
		if flag is False:
			return False, msg
		return True, 'suc'
				
	# 末尾添加模式，不管有无重复index
	def append_csvfile(self, add_record_list, file_path, file_name):
		complete_path = os.path.join(file_path, file_name)
		# 自动建立新的文件
		if not os.path.exists(file_path):
			try:
				os.makedirs(file_path)
			except OSError, e:
				return False, 'create path failed: %s'%e
		record_str_list = self.record_list2str_list(add_record_list)
		try:
			old_file = open(complete_path, 'ab')
			old_file.writelines(record_str_list)
			old_file.close()
		except IOError,e:
			return False, 'append failed: %s'%e
		return True, 'suc'
	

if __name__ == '__main__':
	file_path = '/root/cyh/supeanut/CommonLib/FileTool'
	obj = CsvTool()
	#ori_record = [['a','123er4'],['b','qe12e23'],['e','哈哈']]
	ori_record = []
	#ori_record = [['a', '123er4'],['b', 'bbb'],['c','asd'],['d','12eed'],['e','哈']]
	upd_record = [['x','xxx']]
	add_record = [['x','12w']]
	print obj.new_csvfile(ori_record, file_path, 'new_add.csv', )
	print obj.update_csvfile([0], upd_record, file_path, 'new_add.csv')
	print obj.append_csvfile(add_record, file_path, 'new_add.csv')
